package com.sunlg.smarthome.data.remote;

import com.sunlg.smarthome.base.C;
import com.sunlg.smarthome.data.entity.Curtain;
import com.sunlg.smarthome.data.entity.EnvirDevice;
import com.sunlg.smarthome.data.entity.FireDevice;
import com.sunlg.smarthome.data.entity.FireWarning;
import com.sunlg.smarthome.data.entity.Gateway;
import com.sunlg.smarthome.data.entity.Humidity;
import com.sunlg.smarthome.data.entity.Light;
import com.sunlg.smarthome.data.entity.Notification;
import com.sunlg.smarthome.data.entity.Pump;
import com.sunlg.smarthome.data.entity.RainObserver;
import com.sunlg.smarthome.data.entity.SecurityDevice;
import com.sunlg.smarthome.data.entity.SecurityWarning;
import com.sunlg.smarthome.data.entity.TempAndHum;
import com.sunlg.smarthome.data.entity.Temperature;
import com.sunlg.smarthome.data.entity.User;
import com.sunlg.smarthome.data.entity.Warning;

import java.util.List;
import java.util.Map;

import retrofit2.http.FieldMap;
import retrofit2.http.FormUrlEncoded;
import retrofit2.http.GET;
import retrofit2.http.Headers;
import retrofit2.http.POST;
import retrofit2.http.Query;
import rx.Observable;

/**
 * Retrofit请求服务接口
 * Created by sunlg on 2016/11/30.
 */

public interface SHService {

    /**
     * 用户注册
     * @param user
     * @return
     */
    @Headers({"Content-type:application/x-www-form-urlencoded;charset=UTF-8"})
    @FormUrlEncoded
    @POST(C.API.REGISTER)
    Observable<Result> register(@FieldMap Map<String, Object> user);

    /**
     * 用户登录
     * @param user
     * @return
     */
    @Headers({"Content-type:application/x-www-form-urlencoded;charset=UTF-8"})
    @FormUrlEncoded
    @POST(C.API.LOGIN)
    Observable<Result<User>> login(@FieldMap Map<String, Object> user);

    /**
     * 更新用户信息
     * @param user
     * @return
     */
    @FormUrlEncoded
    @POST(C.API.UPDATE_USER)
    Observable<Result<User>> updateUserMsg(@FieldMap Map<String, Object> user);

    /**
     * 用户注销
     * @return
     */
    @GET(C.API.LOGOUT)
    Observable<Result> logout();

    /**
     * 添加照明设备
     * @param light
     * @return
     */
    @FormUrlEncoded
    @POST(C.API.ADD_LIGHT)
    Observable<Result> addLight(@FieldMap Map<String, Object> light);

    /**
     * 打开照明设备
     * @param lightId
     * @param level
     * @return
     */
    @GET(C.API.LIGHT_ON)
    Observable<Result> takeOn(@Query("lightId") Integer lightId,
                              @Query("level") Integer level);

    /**
     * 关闭照明设备
     * @param lightId
     * @return
     */
    @GET(C.API.LIGHT_OFF)
    Observable<Result> takeOff(@Query("lightId") Integer lightId);

    /**
     * 删除照明设备
     * @param lightId
     * @return
     */
    @GET(C.API.DEL_LIGHT)
    Observable<Result> deleteLight(@Query("lightId") Integer lightId);

    /**
     * 获取所有照明设备
     * @return
     */
    @GET(C.API.GET_ALL_LIGHT)
    Observable<Result<List<Light>>> loadAllLight(@Query("gatewayId") int gatewayId);

    /**
     * 添加网关
     * @param paramsMap
     * @return
     */
    @FormUrlEncoded
    @POST(C.API.ADD_GATEWAY)
    Observable<Result> addGateway(@FieldMap Map<String, Object> paramsMap);

    /**
     * 删除网关
     * @param id
     * @return
     */
    @GET(C.API.DEL_GATEWAY)
    Observable<Result> deleteGateway(@Query("id") Integer id);

    /**
     * 绑定网关
     * @param no
     * @param desc
     * @return
     */
    @GET(C.API.BIND_GATEWAY)
    Observable<Result> bindGateway(@Query("no") Integer no,
                                   @Query(value = "desc", encoded = true) String desc);

    /**
     * 根据gatewayId获取网关
     * @param id
     * @return
     */
    @GET(C.API.GET_GATEWAY_BY_ID)
    Observable<Result<Gateway>> getGatewayById(@Query("id") Integer id);

    /**
     * 根据序号no获取网关
     * @param no
     * @return
     */
    @GET(C.API.GET_GATEWAY_BY_NO)
    Observable<Result<Gateway>> getGatewayByNo(@Query("no") Integer no);

    /**
     * 根据userId获取网关
     * @param userId
     * @return
     */
    @GET(C.API.GET_GATEWAY_BY_USERID)
    Observable<Result<List<Gateway>>> getGatewayByUserId(@Query("userId") Integer userId);

    @FormUrlEncoded
    @POST(C.API.UPDATE_GATEWAY)
    Observable<Result> updateGateway(@FieldMap Map<String, Object> gateway);

    /**
     * 添加窗帘
     * @param curtain
     * @return
     */
    @FormUrlEncoded
    @POST(C.API.ADD_CURTAIN)
    Observable<Result> addCurtain(@FieldMap Map<String, Object> curtain);

    /**
     * 根据curtainId删除窗帘
     * @param curtainId
     * @return
     */
    @GET(C.API.DEL_CURTAIN)
    Observable<Result> deleteCurtain(@Query("curtainId") int curtainId);

    /**
     * 收缩窗帘
     * @param curtainId
     * @return
     */
    @GET(C.API.CURTAIN_FOLD)
    Observable<Result> foldCurtain(@Query("curtainId") int curtainId,
                                   @Query("level") int level,
                                   @Query("speed") int speed);

    /**
     * 展开窗帘
     * @param curtainId
     * @param level
     * @return
     */
    @GET(C.API.CURTAIN_UNFOLD)
    Observable<Result> unfoldCurtain(@Query("curtainId") int curtainId,
                                     @Query("level") int level,
                                     @Query("speed") int speed);

    /**
     * 停止窗帘
     * @param curtainId
     * @return
     */
    @GET(C.API.CURTAIN_STOP)
    Observable<Result> stopCurtain(@Query("curtainId") int curtainId);

    /**
     * 获取所有窗帘
     * @return
     */
    @GET(C.API.GET_ALL_CURTAIN)
    Observable<Result<List<Curtain>>> getAllCurtain(@Query("gatewayId") int gatewayId);

    /**
     * 添加环境监控设备
     * @param device
     * @return
     */
    @FormUrlEncoded
    @POST(C.API.ADD_ENVIR_DEVICE)
    Observable<Result> addEnvirDevice(@FieldMap Map<String, Object> device);

    /**
     * 删除环境监控设备
     * @param envirdeviceId
     * @return
     */
    @GET(C.API.DEL_ENVIR_DEVICE)
    Observable<Result> deleteEnvirDevice(@Query("envirdeviceId") int envirdeviceId);

    /**
     * 获取所有环境监控设备
     * @return
     */
    @GET(C.API.GET_ALL_ENVIR_DEVICE)
    Observable<Result<List<EnvirDevice>>> getAllEnvirDevice(@Query("gatewayId") int gatewayId);

    /**
     * 获取温度和湿度
     * @param gatewayId
     * @return
     */
    @GET(C.API.GET_ALL_LATEST_TEMP_HUM)
    Observable<Result<List<TempAndHum>>> getAllTempAndHum(@Query("gatewayId") int gatewayId);

    /**
     * 获取某个时间段的温度
     * @param envirdeviceId
     * @param timeStart  开始时间，以long表示
     * @param timeEnd  结束时间
     * @return
     */
    @GET(C.API.GET_SECTION_TEMP)
    Observable<Result<List<Temperature>>> getSectionTemp(@Query("envirdeviceId") int envirdeviceId,
                                                         @Query("timeStart") long timeStart,
                                                         @Query("timeEnd") long timeEnd);

    /**
     * 获取某个时间段的湿度
     * @param envirdeviceId
     * @param timeStart  开始时间，以long表示
     * @param timeEnd  结束时间
     * @return
     */
    @GET(C.API.GET_SECTION_HUM)
    Observable<Result<List<Humidity>>> getSectionHum(@Query("envirdeviceId") int envirdeviceId,
                                                     @Query("timeStart") long timeStart,
                                                     @Query("timeEnd") long timeEnd);

    @GET(C.API.GET_LATEST_TEMP)
    Observable<Result<Temperature>> getLatestTemp(@Query("envirdeviceId") int envirdeviceId);

    @GET(C.API.GET_LATEST_HUM)
    Observable<Result<Humidity>> getLatestHum(@Query("envirdeviceId") int envirdeviceId);

    @GET(C.API.AIR_CONDITIONER_ON)
    Observable<Result> airConditionerOn();

    @GET(C.API.AIR_CONDITIONER_OFF)
    Observable<Result> airConditionerOff();

    /**
     * 添加安全控制设备
     * @param device
     * @return
     */
    @FormUrlEncoded
    @POST(C.API.ADD_SECURITY_DEVICE)
    Observable<Result> addSecurityDevice(@FieldMap Map<String, Object> device);

    /**
     * 删除安全控制设备
     * @param securityDeviceId
     * @return
     */
    @GET(C.API.DEL_SECURITY_DEVICE)
    Observable<Result> delSecurityDevice(@Query("securityDeviceId") int securityDeviceId);

    /**
     * 获取所有安全控制设备
     * @return
     */
    @GET(C.API.GET_ALL_SECURITY_DEVICE)
    Observable<Result<List<SecurityDevice>>> getAllSecurityDevice(@Query("gatewayId") int gatewayId);

    @GET(C.API.GET_SECURITY_WARNING)
    Observable<Result<Warning>> getLatestSecurityWarning(@Query("deviceId") int deviceId);

    /**
     * 添加防火设备
     * @param device
     * @return
     */
    @FormUrlEncoded
    @POST(C.API.ADD_FIRE_DEVICE)
    Observable<Result> addFireDevice(@FieldMap Map<String, Object> device);

    /**
     * 删除防火设备
     * @param securityDeviceId
     * @return
     */
    @GET(C.API.DEL_SECURITY_DEVICE)
    Observable<Result> delFireDevice(@Query("securityDeviceId") int securityDeviceId);

    /**
     * 获取所有防火设备
     * @return
     */
    @GET(C.API.GET_ALL_FIRE_DEVICE)
    Observable<Result<List<FireDevice>>> getAllFireDevice(@Query("gatewayId") int gatewayId);


    @GET(C.API.GET_FIRE_WARNING)
    Observable<Result<Warning>> getLatestFireWarning(@Query("deviceId") int deviceId);

    @FormUrlEncoded
    @POST(C.API.ADD_PUMP)
    Observable<Result> addPump(@FieldMap Map<String, Object> pump);

    @GET(C.API.DEL_PUMP)
    Observable<Result> delPump(@Query("pumpId") int pumpId);

    @GET(C.API.GET_ALL_PUMP)
    Observable<Result<List<Pump>>> getAllPump(@Query("gatewayId") int gatewayId);

    @FormUrlEncoded
    @POST(C.API.ADD_RAIN_OBSERVER)
    Observable<Result> addRainObserver(@FieldMap Map<String, Object> rainObserver);

    @GET(C.API.DEL_RAIN_OBSERVER)
    Observable<Result> delRainObserver(@Query("rainObserverId") int rainObserverId);

    @GET(C.API.GET_ALL_RAIN_OBSERVER)
    Observable<Result<List<RainObserver>>> getAllRainObserver(@Query("gatewayId") int gatewayId);

    @GET(C.API.START_PUMP)
    Observable<Result> startPump(@Query("pumpId") int pumpId,
                                 @Query("level") int level);

    @GET(C.API.STOP_PUMP)
    Observable<Result> stopPump(@Query("pumpId") int pumpId);

    @GET(C.API.GET_ALL_SECURITY_WARNING)
    Observable<Result<List<SecurityWarning>>> getAllSecurityWarning(@Query("gatewayId") int gatewayId);

    @GET(C.API.GET_ALL_FIRE_WARNING)
    Observable<Result<List<FireWarning>>> getAllFireWarning(@Query("gatewayId") int gatewayId);

    @GET(C.API.GET_ALL_NOTIFICATION)
    Observable<Result<List<Notification>>> getAllNotification(@Query("userId") int userId);

    @GET(C.API.GET_SECURITY_DEVICE)
    Observable<Result<SecurityDevice>> getSecurityDeviceById(@Query("id") int id);

    @GET(C.API.GET_FIRE_DEVICE)
    Observable<Result<FireDevice>> getFireDeviceById(@Query("id") int id);

}
